#!/usr/bin/python3
# -*- coding: utf-8 -*-

import os
import logging
import json
import aiohttp_jinja2
from io import BytesIO
from aiohttp import web

import db
import fileutils
import hlsutils
import blogutils
import settings
from coreweb import query_string

routes = web.RouteTableDef()
module_name = 'file'


@routes.get('/file')
async def root(request):
    params = query_string(request)
    path = params.get('path', '/root')
    data = fileutils.goto_dir(path)
    data = dict(data, **request.app['view_commons'])
    data['mode'] = 'list'
    data['prefix'] = '/file'
    return {'data': data, '__template__': 'file.html'}


@routes.get('/video/play')
async def video(request):
    params = query_string(request)
    path = params.get('path', '/root')
    data = hlsutils.gethls(path)
    data = dict(data, **request.app['view_commons'])
    data = dict(data, **settings.config['hls'])
    data['mode'] = 'video'
    data['prefix'] = '/file'
    return {'data': data, '__template__': 'file.html'}


@routes.get('/%s/view' % module_name)
async def view(request):
    params = query_string(request)
    id = params.get('id', None)
    path = params.get('path', '/root')
    data = {}
    data = dict(data, **request.app['view_commons'])
    blog = None
    result = blogutils.get_blog(path)
    if result['status']:
        blog = result['msg']
    if blog is None:
        blog = db.Blog()
    data['blog'] = blog
    data['mode'] = 'blog_view'
    data['path'] = path[1:].split('/')
    data['prefix'] = '/file'
    return {'data': data, '__template__': 'file.html'}


@routes.get('/%s/edit' % module_name)
async def blog_edit(request):
    params = query_string(request)
    id = params.get('id', None)
    path = params.get('path', '/root')
    data = {}
    data = dict(data, **request.app['view_commons'])
    blog = None
    result = blogutils.get_blog(path)
    if result['status']:
        blog = result['msg']
    if blog is None:
        blog = db.Blog()
    data['blog'] = blog
    data['mode'] = 'blog_edit'
    data['path'] = path[1:].split('/')
    data['prefix'] = '/file'
    return {'data': data, '__template__': 'file.html'}


@routes.post('/%s/edit' % module_name)
async def blog_save(request):
    params = await request.json()
    name = params.get('name', None)
    summary = params.get('summary', None)
    content = params.get('content', None)
    path = params.get('path', '/root')
    if content is None or len(content) <= 0:
        return {'code': -1, 'msg': 'content [%s]: %s' % (params, content)}
    if name is None or len(name) <= 0:
        return {'code': -1, 'msg': 'name [%s]: %s' % (params, name)}
    if summary is None or len(summary) <= 0:
        return {'code': -1, 'msg': 'summary [%s]: %s' % (params, summary)}
    data = {'content': content, 'name': name,
            'summary': summary, 'path': path}

    result = blogutils.save_blog(data, None)
    if result['status']:
        result = fileutils.save_blog(result['msg'])
        if result['status']:
            return {'code': 0, 'msg': result['msg']}
        logging.error('failed to save file[%s]: %s' % (path, result['msg']))
        return {'code': -1, 'msg': 'failed to save file[%s]: %s' % (path, result['msg'])}
    logging.error('failed to save blog[%s]: %s' % (path, result))
    return {'code': -1, 'msg': 'failed to save blog[%s]: %s' % (path, result['msg'])}


@routes.get('/%s/update' % module_name)
async def update(request):
    params = query_string(request)
    path = params['path']
    status = params['status']
    referer = params['referer']
    referer_referer = params['referer_referer']
    poster_referer = params['poster_referer']
    url = None if isinstance(
        params['url'], str) and 'None' == params['url'] else params['url']
    parent, name = path.rsplit('/', 1)
    result = hlsutils.update(parent, name, status,
                             referer, referer_referer, poster_referer, url)
    if result['status']:
        return {'code': 0, 'msg': path}
    logging.error('failed to update hls[%s]: %s' % (path, result['msg']))
    return {'code': -1, 'msg': 'failed to update hls(%s): %s' % (path, result['msg'])}


@routes.get('/file/export')
async def file_export(request):
    params = query_string(request)
    fullpath = params['fullpath']
    result = fileutils.file_export(fullpath)
    if result['status']:
        return {'code': 0, 'msg': json.dumps(result['msg'], ensure_ascii=False)}
    logging.error('failed to export data[%s]: %s' % (fullpath, result['msg']))
    return {'code': -1, 'msg': 'failed to export data file(%s): %s' % (fullpath, result['msg'])}


@routes.post('/%s/import' % module_name)
async def file_import(request):
    params = await request.json()
    data = params['data']
    if len(data) <= 0:
        logging.error('failed to import data: %s' % (data))
        return {'code': -1, 'msg': 'failed to import data %s' % (data)}
    if '\'' in data:
        data = data.replace('\'', '\"').replace('None', 'null')
    result = fileutils.import_data(json.loads(data, encoding='utf-8'))
    if result['status']:
        return {'code': 0, 'msg': '导入数据%s条' % result['msg']}
    logging.error('failed to import data %s: %s' % (data, result['msg']))
    return {'code': -1, 'msg': 'failed to import_data data %s: %s' % (data, result['msg'])}


@routes.get('/%s/getfile' % module_name)
async def get_file(request):
    params = query_string(request)
    fullpath = params['fullpath']
    result = fileutils.get_file(fullpath)
    if result['status']:
        fileitem = result['msg']
        if fileitem.content_type == 'hls':
            result = hlsutils.get_hls(
                '%s/%s' % (result['msg'].path, result['msg'].name))
            if result['status']:
                return {'code': 0, 'msg': result['msg']}
            else:
                logging.error('failed to get hls[%s]: %s' % (
                    path, result['msg']))
                return {'code': -1, 'msg': 'failed to get hls[%s]: %s' % (path, result['msg'])}
    logging.error('failed to get file[%s]: %s' % (path, result['msg']))
    return {'code': -1, 'msg': 'failed to get file[%s]: %s' % (path, result['msg'])}


@routes.get('/%s/mkdir/{name}' % module_name)
async def mkdir(request):
    name = request.match_info['name']
    params = query_string(request)
    parent = params['parent']
    result = fileutils.makedir(parent, name)
    if result['status']:
        return {'code': 0, 'msg': parent}
    logging.error('failed to makedir(%s, %s): %s' %
                  (parent, name, result['msg']))
    return {'code': -1, 'msg': 'failed to makedir(%s, %s): %s' % (parent, name, result['msg'])}


@routes.get('/%s/rename/{name}' % module_name)
async def rename(request):
    name = request.match_info['name']
    params = query_string(request)
    fullpath = params['fullpath']
    result = fileutils.rename(fullpath, name)
    if result['status']:
        return {'code': 0, 'msg': parent}
    logging.error('failed to rename(%s, %s): %s' %
                  (fullpath, name, result['msg']))
    return {'code': -1, 'msg': 'failed to rename(%s, %s): %s' % (fullpath, name, result['msg'])}
